const User = require('../models/User');
const generateToken = require('../utils/generateToken');
const { successResponse, errorResponse } = require('../utils/responses');
const { getWxOpenId } = require('../utils/wechatApi');

/**
 * @desc    注册新用户
 * @route   POST /api/users/register
 * @access  公开
 */
const registerUser = async (req, res) => {
  try {
    const { username, email, password } = req.body;

    // 检查用户是否已存在
    const userExists = await User.findOne({ $or: [{ email }, { username }] });

    if (userExists) {
      return errorResponse(res, 400, '用户已存在', ['邮箱或用户名已被使用']);
    }

    // 创建用户
    const user = await User.create({
      username,
      email,
      password,
    });

    if (user) {
      // 生成令牌
      const token = generateToken(user._id);

      return successResponse(res, 201, '用户注册成功', {
        _id: user._id,
        username: user.username,
        email: user.email,
        role: user.role,
        token
      });
    } else {
      return errorResponse(res, 400, '无效的用户数据');
    }
  } catch (error) {
    console.error(error);
    return errorResponse(res, 500, '服务器错误', [error.message]);
  }
};

/**
 * @desc    用户登录
 * @route   POST /api/users/login
 * @access  公开
 */
const loginUser = async (req, res) => {
  try {
    const { email, password } = req.body;

    // 查找用户
    const user = await User.findOne({ email }).select('+password');

    if (!user) {
      return errorResponse(res, 401, '无效的凭据', ['邮箱或密码不正确']);
    }

    // 比较密码
    const isMatch = await user.matchPassword(password);

    if (!isMatch) {
      return errorResponse(res, 401, '无效的凭据', ['邮箱或密码不正确']);
    }

    // 生成令牌
    const token = generateToken(user._id);

    return successResponse(res, 200, '登录成功', {
      _id: user._id,
      username: user.username,
      email: user.email,
      role: user.role,
      token
    });
  } catch (error) {
    console.error(error);
    return errorResponse(res, 500, '服务器错误', [error.message]);
  }
};

/**
 * @desc    处理微信登录
 * @route   POST /api/users/wx-login
 * @access  公开
 */
const wechatLogin = async (req, res) => {
  try {
    // 添加调试代码：查看当前所有用户
    console.log('===================== 数据库用户记录 =====================');
    const allUsers = await User.find({}).select('_id username nickname openid email');
    console.log(`当前数据库中有 ${allUsers.length} 个用户:`);
    allUsers.forEach(user => {
      console.log(`ID: ${user._id}, 昵称: ${user.nickname}, OpenID: ${user.openid}, 邮箱: ${user.email}`);
    });
    console.log('========================================================');
    
    const { code, userInfo } = req.body;
    if (!code) {
      return errorResponse(res, 400, '缺少微信登录code');
    }
    
    console.log('接收到微信登录请求:', JSON.stringify({ code, userInfo }));
    
    // 处理userInfo对象
    let nickname = '微信用户';
    let avatarUrl = '';
    let gender = undefined;
    let country = '';
    let province = '';
    let city = '';

    if (userInfo) {
      nickname = userInfo.nickName || nickname;
      avatarUrl = userInfo.avatarUrl || avatarUrl;
      gender = userInfo.gender;
      country = userInfo.country || country;
      province = userInfo.province || province;
      city = userInfo.city || city;
    }

    console.log('处理后的用户信息:', { nickname, gender, country, province, city });
    
    // 获取openid的逻辑
    let openid;
    
    if (process.env.NODE_ENV === 'production') {
      // 生产环境: 调用微信API获取openid
      try {
        const wxResponse = await getWxOpenId(code);
        openid = wxResponse.openid;
        if (!openid) {
          console.error('微信API返回的数据中没有openid:', wxResponse);
          return errorResponse(res, 500, '无法获取微信用户标识');
        }
      } catch (error) {
        console.error('调用微信API获取openid失败:', error);
        return errorResponse(res, 500, '微信登录失败', [error.message]);
      }
    } else {
      // 开发环境: 使用固定的测试openid或基于用户信息生成更稳定的openid
      if (userInfo && userInfo.nickName) {
        // 添加时间戳和随机字符串，确保每次登录生成不同的openid
        const timestamp = Date.now();
        const randomStr = Math.random().toString(36).substring(2, 8);
        openid = `dev_${userInfo.nickName.replace(/\s+/g, '_')}_${timestamp}_${randomStr}`;
      } else {
        // 使用时间戳和随机数生成唯一的测试openid
        const timestamp = Date.now();
        const randomStr = Math.random().toString(36).substring(2, 8);
        openid = `dev_test_${timestamp}_${randomStr}`;
      }
    }
    
    console.log('使用的openid:', openid);
    
    // 查找或创建用户
    let user = await User.findOne({ openid });
    
    if (!user) {
      console.log('用户不存在，创建新用户');
      
      // 创建新用户，注意性别字段的处理
      // 由于需要准确的性别信息，当无法从微信获取时设置为'未知'
      let genderValue = '未知'; // 默认值为'未知'
      if (gender === 1) {
        genderValue = '男';
      } else if (gender === 2) {
        genderValue = '女';
      }
      
      // 生成唯一的用户名和临时邮箱
      const uniqueId = `${Date.now()}_${Math.floor(Math.random() * 10000)}`;
      const username = `wx_user_${uniqueId}`;
      // 创建一个符合邮箱格式的临时邮箱，用户后续可以更新
      const tempEmail = `temp_${uniqueId}@example.com`;
      
      // 创建新用户
      user = new User({
        openid,
        nickname: nickname,
        avatarUrl: avatarUrl,
        gender: genderValue, // 使用处理后的性别值
        country: country,
        province: province,
        city: city,
        username: username,
        email: tempEmail, // 使用临时邮箱而不是null
        isProfileComplete: false
      });
      
      try {
        await user.save();
        console.log('新用户创建成功:', user._id);
      } catch (err) {
        console.error('创建用户失败:', err);
        console.error('详细错误信息:', {
          name: err.name,
          message: err.message,
          code: err.code,
          keyPattern: err.keyPattern,
          keyValue: err.keyValue
        });
        
        // 如果是唯一性约束错误(代码为11000)
        if (err.code === 11000) {
          console.log('尝试查找现有用户并使用该用户登录');
          
          try {
            // 更灵活的查找方式 - 首先尝试基于nickName
            let existingUser = null;
            
            if (userInfo && userInfo.nickName) {
              existingUser = await User.findOne({ 
                nickname: userInfo.nickName
              });
            }
            
            // 如果基于昵称没找到，尝试查找相似openid
            if (!existingUser) {
              const openidPattern = userInfo && userInfo.nickName 
                ? new RegExp(`^dev_${userInfo.nickName.replace(/\s+/g, '_')}`) 
                : new RegExp('^dev_test');
                
              existingUser = await User.findOne({ openid: openidPattern });
            }
            
            // 如果仍未找到，尝试查找任何可用的测试账号
            if (!existingUser) {
              existingUser = await User.findOne({ openid: /^dev_/ });
            }
            
            if (existingUser) {
              console.log('找到现有用户，使用该用户:', existingUser._id);
              const token = generateToken(existingUser._id);
              return successResponse(res, 200, '微信登录成功(使用现有账号)', {
                _id: existingUser._id,
                openid: existingUser.openid,
                nickname: existingUser.nickname,
                avatarUrl: existingUser.avatarUrl,
                isProfileComplete: existingUser.isProfileComplete,
                token
              });
            }
          } catch (findErr) {
            console.error('查找现有用户失败:', findErr);
          }
        }
        
        return errorResponse(res, 500, '创建用户失败', [err.message]);
      }
    } else {
      console.log('用户已存在:', user._id);
      
      // 更新用户信息(如果提供了)
      if (nickname) {
        // 处理性别字段
        let genderValue = user.gender; // 保留原有值
        if (gender === 1) {
          genderValue = '男';
        } else if (gender === 2) {
          genderValue = '女';
        } else if (gender === 0 || gender === undefined) {
          // 如果微信没有提供性别信息，只有在用户之前没有设置性别时才设为'未知'
          if (user.gender === '保密') {
            genderValue = '未知';
          }
        }
        
        // 只有在信息有变化时才更新
        if (
          user.nickname !== nickname || 
          user.avatarUrl !== avatarUrl ||
          genderValue !== user.gender ||
          user.country !== country ||
          user.province !== province ||
          user.city !== city
        ) {
          user.nickname = nickname;
          user.avatarUrl = avatarUrl;
          user.gender = genderValue;
          user.country = country || user.country;
          user.province = province || user.province;
          user.city = city || user.city;
          
          try {
            await user.save();
            console.log('用户信息已更新');
          } catch (err) {
            console.error('更新用户信息失败:', err);
            return errorResponse(res, 500, '更新用户信息失败', [err.message]);
          }
        }
      }
    }
    
    // 生成JWT令牌
    const token = generateToken(user._id);
    console.log('生成token成功:', token.substring(0, 20) + '...');
    
    // 返回用户信息与令牌
    return successResponse(res, 200, '微信登录成功', {
      _id: user._id,
      openid: user.openid,
      nickname: user.nickname,
      avatarUrl: user.avatarUrl,
      isProfileComplete: user.isProfileComplete,
      token
    });
    
  } catch (error) {
    console.error('微信登录失败:', error);
    return errorResponse(res, 500, '服务器错误', [error.message]);
  }
};

/**
 * @desc    获取当前用户资料
 * @route   GET /api/users/profile
 * @access  私有
 */
const getUserProfile = async (req, res) => {
  try {
    const user = await User.findById(req.user.id);

    if (!user) {
      return errorResponse(res, 404, '用户不存在');
    }

    return successResponse(res, 200, '获取用户资料成功', {
      _id: user._id,
      username: user.username,
      email: user.email,
      name: user.name,
      gender: user.gender,
      birthDate: user.birthDate,
      height: user.height,
      weight: user.weight,
      waistline: user.waistline,
      bmi: user.bmi,
      bloodType: user.bloodType,
      diabetesType: user.diabetesType,
      diagnosisDate: user.diagnosisDate,
      hasHypertension: user.hasHypertension,
      hasHeartDisease: user.hasHeartDisease,
      hasKidneyDisease: user.hasKidneyDisease,
      familyDiabetes: user.familyDiabetes,
      medications: user.medications, 
      role: user.role,
      nickname: user.nickname,
      phoneNumber: user.phoneNumber,
      avatarUrl: user.avatarUrl,
      isProfileComplete: user.isProfileComplete,
      physiologicalStatus: user.physiologicalStatus,
      activityLevel: user.activityLevel,
      nutritionTarget: user.nutritionTarget,
      createdAt: user.createdAt
    });
  } catch (error) {
    console.error(error);
    return errorResponse(res, 500, '服务器错误', [error.message]);
  }
};

/**
 * @desc    更新用户健康资料
 * @route   PUT /api/users/health-profile
 * @access  私有
 */
const updateHealthProfile = async (req, res) => {
  try {
    const user = await User.findById(req.user.id);

    if (!user) {
      return errorResponse(res, 404, '用户不存在');
    }

    // 更新健康相关信息
    const { gender, birthDate, height, diabetesType, diagnosisDate } = req.body;
    
    if (gender) user.gender = gender;
    if (birthDate) user.birthDate = birthDate;
    if (height) user.height = height;
    if (diabetesType) user.diabetesType = diabetesType;
    if (diagnosisDate) user.diagnosisDate = diagnosisDate;
    
    // 标记健康资料已完成设置
    user.isProfileComplete = true;

    const updatedUser = await user.save();

    return successResponse(res, 200, '更新健康资料成功', {
      _id: updatedUser._id,
      gender: updatedUser.gender,
      birthDate: updatedUser.birthDate,
      height: updatedUser.height,
      diabetesType: updatedUser.diabetesType,
      diagnosisDate: updatedUser.diagnosisDate,
      isProfileComplete: updatedUser.isProfileComplete
    });
  } catch (error) {
    console.error(error);
    return errorResponse(res, 500, '服务器错误', [error.message]);
  }
};

/**
 * @desc    更新用户资料
 * @route   PUT /api/users/profile
 * @access  私有
 */
const updateUserProfile = async (req, res) => {
  try {
    const user = await User.findById(req.user.id);

    if (!user) {
      return errorResponse(res, 404, '用户不存在');
    }

    // 验证输入数据
    const validationErrors = validateUserData(req.body);
    if (validationErrors.length > 0) {
      return errorResponse(res, 400, '输入数据无效', validationErrors);
    }
    
    console.log('更新用户信息:', req.body);
    console.log('生理状况:', req.body.physiologicalStatus);
    console.log('体力活动水平:', req.body.activityLevel);

    // 更新用户信息
    user.name = req.body.name || user.name;
    user.gender = req.body.gender || user.gender;
    user.birthDate = req.body.birthDate || user.birthDate;
    user.nickname = req.body.nickname || user.nickname;
    
    // 更新头像URL
    if (req.body.avatarUrl) user.avatarUrl = req.body.avatarUrl;
    
    // 更新联系电话
    if (req.body.phoneNumber !== undefined) user.phoneNumber = req.body.phoneNumber;
    
    // 正确处理数值类型的健康数据
    if (req.body.height !== undefined) user.height = req.body.height;
    if (req.body.weight !== undefined) user.weight = req.body.weight;
    if (req.body.waistline !== undefined) user.waistline = req.body.waistline;
    if (req.body.bmi !== undefined) user.bmi = req.body.bmi;
    
    user.diabetesType = req.body.diabetesType || user.diabetesType;
    user.diagnosisDate = req.body.diagnosisDate || user.diagnosisDate;
    
    // 更新生理状况和体力活动水平
    if (req.body.physiologicalStatus) {
      if (['normal', 'pregnant_early', 'pregnant_mid', 'pregnant_late', 'breastfeeding'].includes(req.body.physiologicalStatus)) {
        user.physiologicalStatus = req.body.physiologicalStatus;
      }
    }
    
    if (req.body.activityLevel) {
      if (['light', 'moderate', 'heavy'].includes(req.body.activityLevel)) {
        user.activityLevel = req.body.activityLevel;
      }
    }
    
    // 更新其他健康相关字段
    if (req.body.hasHypertension !== undefined) user.hasHypertension = req.body.hasHypertension;
    if (req.body.hasHeartDisease !== undefined) user.hasHeartDisease = req.body.hasHeartDisease;
    if (req.body.hasKidneyDisease !== undefined) user.hasKidneyDisease = req.body.hasKidneyDisease;
    if (req.body.familyDiabetes !== undefined) user.familyDiabetes = req.body.familyDiabetes;
    if (req.body.medications) user.medications = req.body.medications;
    if (req.body.bloodType) user.bloodType = req.body.bloodType;

    // 如果提供了邮箱，则更新
    if (req.body.email && req.body.email !== user.email) {
      // 检查邮箱是否已被其他用户使用
      const emailExists = await User.findOne({ email: req.body.email });
      if (emailExists && emailExists._id.toString() !== user._id.toString()) {
        return errorResponse(res, 400, '邮箱已被使用');
      }
      user.email = req.body.email;
    }

    // 如果提供了密码，则更新
    if (req.body.password) {
      user.password = req.body.password;
    }

    // 保存用户，触发pre save钩子来计算营养目标
    const updatedUser = await user.save();
    console.log('更新后的用户数据:', {
      physiologicalStatus: updatedUser.physiologicalStatus,
      activityLevel: updatedUser.activityLevel,
      nutritionTarget: updatedUser.nutritionTarget
    });

    return successResponse(res, 200, '更新用户资料成功', {
      _id: updatedUser._id,
      username: updatedUser.username,
      email: updatedUser.email,
      name: updatedUser.name,
      gender: updatedUser.gender,
      birthDate: updatedUser.birthDate,
      height: updatedUser.height,
      weight: updatedUser.weight,
      waistline: updatedUser.waistline,
      bmi: updatedUser.bmi,
      diabetesType: updatedUser.diabetesType,
      diagnosisDate: updatedUser.diagnosisDate,
      nickname: updatedUser.nickname,
      phoneNumber: updatedUser.phoneNumber,
      avatarUrl: updatedUser.avatarUrl,
      isProfileComplete: updatedUser.isProfileComplete,
      role: updatedUser.role,
      // 返回新增字段
      physiologicalStatus: updatedUser.physiologicalStatus,
      activityLevel: updatedUser.activityLevel,
      // 返回计算得到的营养目标
      nutritionTarget: updatedUser.nutritionTarget
    });
  } catch (error) {
    console.error(error);
    return errorResponse(res, 500, '服务器错误', [error.message]);
  }
};

/**
 * 验证用户数据
 * @param {Object} data - 要验证的用户数据
 * @returns {Array} - 验证错误信息数组
 */
function validateUserData(data) {
  const errors = [];
  
  // 调试日志，查看接收到的数据
  console.log('验证用户数据:', JSON.stringify(data));
  
  // 验证性别 - 放宽验证条件，允许数字类型
  if (data.gender !== undefined && data.gender !== null && 
      typeof data.gender !== 'number' && 
      !['男', '女', '其他', '未知', '保密', '1', '2'].includes(data.gender)) {
    errors.push('性别必须是：男、女、其他、未知或保密');
  }
  
  // 验证年龄 - 如果提供了年龄，才验证
  if (data.age !== undefined && data.age !== null && data.age !== '') {
    const age = Number(data.age);
    if (isNaN(age) || age < 0 || age > 150) {
      errors.push('年龄必须是0-150之间的数字');
    }
  }
  
  // 验证身高
  if (data.height !== undefined && data.height !== null && data.height !== '') {
    const height = Number(data.height);
    if (isNaN(height) || height < 30 || height > 250) {
      errors.push('身高必须是30-250cm之间的数字');
    }
  }
  
  // 验证体重
  if (data.weight !== undefined && data.weight !== null && data.weight !== '') {
    const weight = Number(data.weight);
    if (isNaN(weight) || weight < 2 || weight > 300) {
      errors.push('体重必须是2-300kg之间的数字');
    }
  }
  
  // 验证腰围
  if (data.waistline !== undefined && data.waistline !== null && data.waistline !== '') {
    const waistline = Number(data.waistline);
    if (isNaN(waistline) || waistline < 30 || waistline > 200) {
      errors.push('腰围必须是30-200cm之间的数字');
    }
  }
  
  // 验证手机号码
  if (data.phoneNumber) {
    const phoneRegex = /^1[3-9]\d{9}$/;
    if (!phoneRegex.test(data.phoneNumber)) {
      errors.push('请输入有效的手机号码');
    }
  }
  
  // 验证血型
  if (data.bloodType) {
    console.log('验证血型:', data.bloodType, '类型:', typeof data.bloodType);
    const validBloodTypes = ['A型', 'B型', 'AB型', 'O型', 'A', 'B', 'AB', 'O'];
    if (!validBloodTypes.includes(data.bloodType)) {
      errors.push('血型必须是A型、B型、AB型或O型');
    }
  }
  
  // 验证糖尿病类型
  if (data.diabetesType && !['1型', '2型', '妊娠期', '前期', '无', '其他'].includes(data.diabetesType)) {
    errors.push('糖尿病类型必须是1型、2型、妊娠期、前期、无或其他');
  }
  
  // 验证出生日期
  if (data.birthDate) {
    try {
      const birthDate = new Date(data.birthDate);
      if (isNaN(birthDate.getTime())) {
        errors.push('出生日期格式无效');
      } else {
        const today = new Date();
        const minDate = new Date('1900-01-01');
        
        if (birthDate > today) {
          errors.push('出生日期不能超过今天');
        }
        
        if (birthDate < minDate) {
          errors.push('出生日期不能早于1900年');
        }
      }
    } catch (err) {
      errors.push('出生日期格式无效');
    }
  }
  
  console.log('验证错误:', errors);
  return errors;
}

module.exports = {
  registerUser,
  loginUser,
  wechatLogin,
  getUserProfile,
  updateUserProfile,
  updateHealthProfile
}; 